From 427deb4f13fbe8b9ef437edf113162f9219c4a54 Mon Sep 17 00:00:00 2001 From: Benjamin Otte Date: Tue, 15 Oct 2019 15:34:16 +0200 Subject: [PATCH] widget: Make gtk_widget_grab_focus() return a boolean So now it can actually fail. It doesn't yet though. --- demos/gtk-demo/demotaggedentry.c | 4 ++-- gtk/gtkcombobox.c | 10 ++++++---- gtk/gtkentry.c | 4 ++-- gtk/gtkfilechooserentry.c | 9 ++++++--- gtk/gtklabel.c | 11 +++++++---- gtk/gtklistbox.c | 9 ++++++--- gtk/gtkpasswordentry.c | 4 ++-- gtk/gtksearchentry.c | 4 ++-- gtk/gtkspinbutton.c | 8 +++----- gtk/gtktext.c | 17 +++++++++++------ gtk/gtktext.h | 2 +- gtk/gtktreeview.c | 17 ++++++++--------- gtk/gtkwidget.c | 30 ++++++++++++++++++++---------- gtk/gtkwidget.h | 4 ++-- 14 files changed, 78 insertions(+), 55 deletions(-) diff --git a/demos/gtk-demo/demotaggedentry.c b/demos/gtk-demo/demotaggedentry.c index f74ee774e4..dcba5a435d 100644 --- a/demos/gtk-demo/demotaggedentry.c +++ b/demos/gtk-demo/demotaggedentry.c @@ -129,13 +129,13 @@ demo_tagged_entry_size_allocate (GtkWidget *widget, baseline); } -static void +static gboolean demo_tagged_entry_grab_focus (GtkWidget *widget) { DemoTaggedEntry *entry = DEMO_TAGGED_ENTRY (widget); DemoTaggedEntryPrivate *priv = demo_tagged_entry_get_instance_private (entry); - gtk_widget_grab_focus (priv->entry); + return gtk_widget_grab_focus (priv->entry); } static void diff --git a/gtk/gtkcombobox.c b/gtk/gtkcombobox.c index 7ccad72ed7..c10a6835ce 100644 --- a/gtk/gtkcombobox.c +++ b/gtk/gtkcombobox.c @@ -215,7 +215,7 @@ static void gtk_combo_box_get_property (GObject *object, GValue *value, GParamSpec *spec); -static void gtk_combo_box_grab_focus (GtkWidget *widget); +static gboolean gtk_combo_box_grab_focus (GtkWidget *widget); static void gtk_combo_box_button_toggled (GtkWidget *widget, gpointer data); static void gtk_combo_box_add (GtkContainer *container, @@ -2323,7 +2323,7 @@ gtk_combo_box_mnemonic_activate (GtkWidget *widget, return TRUE; } -static void +static gboolean gtk_combo_box_grab_focus (GtkWidget *widget) { GtkComboBox *combo_box = GTK_COMBO_BOX (widget); @@ -2335,10 +2335,12 @@ gtk_combo_box_grab_focus (GtkWidget *widget) child = gtk_bin_get_child (GTK_BIN (combo_box)); if (child) - gtk_widget_grab_focus (child); + return gtk_widget_grab_focus (child); + else + return FALSE; } else - gtk_widget_grab_focus (priv->button); + return gtk_widget_grab_focus (priv->button); } static void diff --git a/gtk/gtkentry.c b/gtk/gtkentry.c index a2ebe7110b..778e0b0657 100644 --- a/gtk/gtkentry.c +++ b/gtk/gtkentry.c @@ -302,13 +302,13 @@ G_DEFINE_TYPE_WITH_CODE (GtkEntry, gtk_entry, GTK_TYPE_WIDGET, G_IMPLEMENT_INTERFACE (GTK_TYPE_CELL_EDITABLE, gtk_entry_cell_editable_init)) -static void +static gboolean gtk_entry_grab_focus (GtkWidget *widget) { GtkEntry *entry = GTK_ENTRY (widget); GtkEntryPrivate *priv = gtk_entry_get_instance_private (entry); - gtk_widget_grab_focus (priv->text); + return gtk_widget_grab_focus (priv->text); } static gboolean diff --git a/gtk/gtkfilechooserentry.c b/gtk/gtkfilechooserentry.c index ef193d1357..2c8a73f0c8 100644 --- a/gtk/gtkfilechooserentry.c +++ b/gtk/gtkfilechooserentry.c @@ -83,7 +83,7 @@ static guint signals[LAST_SIGNAL] = { 0 }; static void gtk_file_chooser_entry_finalize (GObject *object); static void gtk_file_chooser_entry_dispose (GObject *object); -static void gtk_file_chooser_entry_grab_focus (GtkWidget *widget); +static gboolean gtk_file_chooser_entry_grab_focus (GtkWidget *widget); static gboolean gtk_file_chooser_entry_tab_handler (GtkEventControllerKey *key, guint keyval, guint keycode, @@ -497,11 +497,14 @@ explicitly_complete (GtkFileChooserEntry *chooser_entry) gtk_widget_error_bell (GTK_WIDGET (chooser_entry)); } -static void +static gboolean gtk_file_chooser_entry_grab_focus (GtkWidget *widget) { - GTK_WIDGET_CLASS (_gtk_file_chooser_entry_parent_class)->grab_focus (widget); + if (!GTK_WIDGET_CLASS (_gtk_file_chooser_entry_parent_class)->grab_focus (widget)) + return FALSE; + _gtk_file_chooser_entry_select_filename (GTK_FILE_CHOOSER_ENTRY (widget)); + return TRUE; } static void diff --git a/gtk/gtklabel.c b/gtk/gtklabel.c index 8e5573a967..11133df6e2 100644 --- a/gtk/gtklabel.c +++ b/gtk/gtklabel.c @@ -455,7 +455,7 @@ static void gtk_label_leave (GtkEventControllerMotion *controller, GdkNotifyType detail, gpointer data); -static void gtk_label_grab_focus (GtkWidget *widget); +static gboolean gtk_label_grab_focus (GtkWidget *widget); static gboolean gtk_label_query_tooltip (GtkWidget *widget, gint x, @@ -4272,7 +4272,7 @@ gtk_label_select_word (GtkLabel *label) gtk_label_select_region_index (label, min, max); } -static void +static gboolean gtk_label_grab_focus (GtkWidget *widget) { GtkLabel *label = GTK_LABEL (widget); @@ -4282,9 +4282,10 @@ gtk_label_grab_focus (GtkWidget *widget) GList *l; if (priv->select_info == NULL) - return; + return FALSE; - GTK_WIDGET_CLASS (gtk_label_parent_class)->grab_focus (widget); + if (!GTK_WIDGET_CLASS (gtk_label_parent_class)->grab_focus (widget)) + return FALSE; if (priv->select_info->selectable) { @@ -4313,6 +4314,8 @@ gtk_label_grab_focus (GtkWidget *widget) } } } + + return TRUE; } static gboolean diff --git a/gtk/gtklistbox.c b/gtk/gtklistbox.c index 857da444c7..0a85405d5b 100644 --- a/gtk/gtklistbox.c +++ b/gtk/gtklistbox.c @@ -3409,18 +3409,21 @@ gtk_list_box_row_dispose (GObject *object) G_OBJECT_CLASS (gtk_list_box_row_parent_class)->dispose (object); } -static void +static gboolean gtk_list_box_row_grab_focus (GtkWidget *widget) { GtkListBoxRow *row = GTK_LIST_BOX_ROW (widget); GtkListBox *box = gtk_list_box_row_get_box (row); - g_return_if_fail (box != NULL); + g_return_val_if_fail (box != NULL, FALSE); + + if (!GTK_WIDGET_CLASS (gtk_list_box_row_parent_class)->grab_focus (widget)) + return FALSE; if (BOX_PRIV (box)->cursor_row != row) gtk_list_box_update_cursor (box, row, FALSE); - GTK_WIDGET_CLASS (gtk_list_box_row_parent_class)->grab_focus (widget); + return TRUE; } static void diff --git a/gtk/gtkpasswordentry.c b/gtk/gtkpasswordentry.c index d8ed6a90e8..99717faf37 100644 --- a/gtk/gtkpasswordentry.c +++ b/gtk/gtkpasswordentry.c @@ -346,13 +346,13 @@ gtk_password_entry_get_accessible (GtkWidget *widget) return atk_obj; } -static void +static gboolean gtk_password_entry_grab_focus (GtkWidget *widget) { GtkPasswordEntry *entry = GTK_PASSWORD_ENTRY (widget); GtkPasswordEntryPrivate *priv = gtk_password_entry_get_instance_private (entry); - gtk_widget_grab_focus (priv->entry); + return gtk_widget_grab_focus (priv->entry); } static gboolean diff --git a/gtk/gtksearchentry.c b/gtk/gtksearchentry.c index 1377aa312c..06460e6282 100644 --- a/gtk/gtksearchentry.c +++ b/gtk/gtksearchentry.c @@ -241,13 +241,13 @@ gtk_search_entry_get_accessible (GtkWidget *widget) return atk_obj; } -static void +static gboolean gtk_search_entry_grab_focus (GtkWidget *widget) { GtkSearchEntry *entry = GTK_SEARCH_ENTRY (widget); GtkSearchEntryPrivate *priv = gtk_search_entry_get_instance_private (entry); - gtk_text_grab_focus_without_selecting (GTK_TEXT (priv->entry)); + return gtk_text_grab_focus_without_selecting (GTK_TEXT (priv->entry)); } static gboolean diff --git a/gtk/gtkspinbutton.c b/gtk/gtkspinbutton.c index ce51cdb29d..b7a460cfd3 100644 --- a/gtk/gtkspinbutton.c +++ b/gtk/gtkspinbutton.c @@ -317,13 +317,13 @@ G_DEFINE_TYPE_WITH_CODE (GtkSpinButton, gtk_spin_button, GTK_TYPE_WIDGET, GTK_TYPE_SCROLL_TYPE, scroll) -static void +static gboolean gtk_spin_button_grab_focus (GtkWidget *widget) { GtkSpinButton *spin_button = GTK_SPIN_BUTTON (widget); GtkSpinButtonPrivate *priv = gtk_spin_button_get_instance_private (spin_button); - gtk_widget_grab_focus (priv->entry); + return gtk_widget_grab_focus (priv->entry); } static gboolean @@ -333,9 +333,7 @@ gtk_spin_button_mnemonic_activate (GtkWidget *widget, GtkSpinButton *spin_button = GTK_SPIN_BUTTON (widget); GtkSpinButtonPrivate *priv = gtk_spin_button_get_instance_private (spin_button); - gtk_widget_grab_focus (priv->entry); - - return TRUE; + return gtk_widget_grab_focus (priv->entry); } static void diff --git a/gtk/gtktext.c b/gtk/gtktext.c index ffe683fed7..6627fee23e 100644 --- a/gtk/gtktext.c +++ b/gtk/gtktext.c @@ -321,7 +321,7 @@ static void gtk_text_snapshot (GtkWidget *widget, GtkSnapshot *snapshot); static void gtk_text_focus_in (GtkWidget *widget); static void gtk_text_focus_out (GtkWidget *widget); -static void gtk_text_grab_focus (GtkWidget *widget); +static gboolean gtk_text_grab_focus (GtkWidget *widget); static void gtk_text_style_updated (GtkWidget *widget); static void gtk_text_direction_changed (GtkWidget *widget, GtkTextDirection previous_dir); @@ -3017,14 +3017,15 @@ gtk_text_focus_out (GtkWidget *widget) g_signal_handlers_disconnect_by_func (keymap, keymap_direction_changed, self); } -static void +static gboolean gtk_text_grab_focus (GtkWidget *widget) { GtkText *self = GTK_TEXT (widget); GtkTextPrivate *priv = gtk_text_get_instance_private (self); gboolean select_on_focus; - GTK_WIDGET_CLASS (gtk_text_parent_class)->grab_focus (GTK_WIDGET (self)); + if (!GTK_WIDGET_CLASS (gtk_text_parent_class)->grab_focus (GTK_WIDGET (self))) + return FALSE; if (priv->editable && !priv->in_click) { @@ -3036,6 +3037,8 @@ gtk_text_grab_focus (GtkWidget *widget) if (select_on_focus) gtk_text_set_selection_bounds (self, 0, -1); } + + return TRUE; } /** @@ -3049,13 +3052,15 @@ gtk_text_grab_focus (GtkWidget *widget) * You only want to call this on some special entries * which the user usually doesn't want to replace all text in, * such as search-as-you-type entries. + * + * Returns: %TRUE if focus is now inside @self */ -void +gboolean gtk_text_grab_focus_without_selecting (GtkText *self) { - g_return_if_fail (GTK_IS_TEXT (self)); + g_return_val_if_fail (GTK_IS_TEXT (self), FALSE); - GTK_WIDGET_CLASS (gtk_text_parent_class)->grab_focus (GTK_WIDGET (self)); + return GTK_WIDGET_CLASS (gtk_text_parent_class)->grab_focus (GTK_WIDGET (self)); } static void diff --git a/gtk/gtktext.h b/gtk/gtktext.h index 025fdd3d89..4ce0b781bb 100644 --- a/gtk/gtktext.h +++ b/gtk/gtktext.h @@ -132,7 +132,7 @@ GDK_AVAILABLE_IN_ALL PangoTabArray * gtk_text_get_tabs (GtkText *self); GDK_AVAILABLE_IN_ALL -void gtk_text_grab_focus_without_selecting (GtkText *self); +gboolean gtk_text_grab_focus_without_selecting (GtkText *self); GDK_AVAILABLE_IN_ALL void gtk_text_set_extra_menu (GtkText *self, diff --git a/gtk/gtktreeview.c b/gtk/gtktreeview.c index aa449479ae..647d2e1440 100644 --- a/gtk/gtktreeview.c +++ b/gtk/gtktreeview.c @@ -669,7 +669,7 @@ static void gtk_tree_view_key_controller_focus_out (GtkEventControllerKey static gint gtk_tree_view_focus (GtkWidget *widget, GtkDirectionType direction); -static void gtk_tree_view_grab_focus (GtkWidget *widget); +static gboolean gtk_tree_view_grab_focus (GtkWidget *widget); static void gtk_tree_view_style_updated (GtkWidget *widget); /* container signals */ @@ -8033,8 +8033,7 @@ gtk_tree_view_focus (GtkWidget *widget, return FALSE; case GTK_DIR_TAB_FORWARD: case GTK_DIR_DOWN: - gtk_widget_grab_focus (widget); - return TRUE; + return gtk_widget_grab_focus (widget); default: g_assert_not_reached (); return FALSE; @@ -8044,8 +8043,7 @@ gtk_tree_view_focus (GtkWidget *widget, /* Case 2. We don't have focus at all. */ if (!gtk_widget_has_focus (widget)) { - gtk_widget_grab_focus (widget); - return TRUE; + return gtk_widget_grab_focus (widget); } /* Case 3. We have focus already. */ @@ -8055,16 +8053,17 @@ gtk_tree_view_focus (GtkWidget *widget, return FALSE; /* Other directions caught by the keybindings */ - gtk_widget_grab_focus (widget); - return TRUE; + return gtk_widget_grab_focus (widget); } -static void +static gboolean gtk_tree_view_grab_focus (GtkWidget *widget) { - GTK_WIDGET_CLASS (gtk_tree_view_parent_class)->grab_focus (widget); + if (!GTK_WIDGET_CLASS (gtk_tree_view_parent_class)->grab_focus (widget)) + return FALSE; gtk_tree_view_focus_to_cursor (GTK_TREE_VIEW (widget)); + return TRUE; } static void diff --git a/gtk/gtkwidget.c b/gtk/gtkwidget.c index 7780f0ded0..5201785480 100644 --- a/gtk/gtkwidget.c +++ b/gtk/gtkwidget.c @@ -623,7 +623,7 @@ static void gtk_widget_real_size_allocate (GtkWidget *widget, static void gtk_widget_real_direction_changed(GtkWidget *widget, GtkTextDirection previous_direction); -static void gtk_widget_real_grab_focus (GtkWidget *focus_widget); +static gboolean gtk_widget_real_grab_focus (GtkWidget *focus_widget); static gboolean gtk_widget_real_query_tooltip (GtkWidget *widget, gint x, gint y, @@ -5139,7 +5139,7 @@ gtk_widget_real_mnemonic_activate (GtkWidget *widget, if (!group_cycling && GTK_WIDGET_GET_CLASS (widget)->activate_signal) gtk_widget_activate (widget); else if (gtk_widget_get_can_focus (widget)) - gtk_widget_grab_focus (widget); + return gtk_widget_grab_focus (widget); else { g_warning ("widget '%s' isn't suitable for mnemonic activation", @@ -5411,23 +5411,33 @@ _gtk_widget_grab_notify (GtkWidget *widget, * Causes @widget (or one of its descendents) to have the keyboard focus * for the #GtkWindow it's inside. * - * @widget must be focusable, or have a ::grab_focus implementation that - * transfers the focus to a descendant of @widget that is focusable. + * If @widget is not focusable, or its ::grab_focus implementation cannot + * transfer the focus to a descendant of @widget that is focusable, it will + * not take focus and %FALSE will be returned. + * + * Calling gtk_widget_grab_focus() on an already focused widget is allowed, + * should not have an effect, and return %TRUE. + * + * Returns: %TRUE if focus is now inside @widget. **/ -void +gboolean gtk_widget_grab_focus (GtkWidget *widget) { - g_return_if_fail (GTK_IS_WIDGET (widget)); + g_return_val_if_fail (GTK_IS_WIDGET (widget), FALSE); - GTK_WIDGET_GET_CLASS (widget)->grab_focus (widget); + return GTK_WIDGET_GET_CLASS (widget)->grab_focus (widget); } -static void +static gboolean gtk_widget_real_grab_focus (GtkWidget *focus_widget) { GtkWidgetPrivate *priv = gtk_widget_get_instance_private (focus_widget); - if (priv->root) - gtk_root_set_focus (priv->root, focus_widget); + + if (!priv->root) + return FALSE; + + gtk_root_set_focus (priv->root, focus_widget); + return TRUE; } static gboolean diff --git a/gtk/gtkwidget.h b/gtk/gtkwidget.h index 67b752edf0..49cf371cf4 100644 --- a/gtk/gtkwidget.h +++ b/gtk/gtkwidget.h @@ -266,7 +266,7 @@ struct _GtkWidgetClass gboolean group_cycling); /* explicit focus */ - void (* grab_focus) (GtkWidget *widget); + gboolean (* grab_focus) (GtkWidget *widget); gboolean (* focus) (GtkWidget *widget, GtkDirectionType direction); @@ -460,7 +460,7 @@ gboolean gtk_widget_is_focus (GtkWidget *widget); GDK_AVAILABLE_IN_ALL gboolean gtk_widget_has_visible_focus (GtkWidget *widget); GDK_AVAILABLE_IN_ALL -void gtk_widget_grab_focus (GtkWidget *widget); +gboolean gtk_widget_grab_focus (GtkWidget *widget); GDK_AVAILABLE_IN_ALL void gtk_widget_set_focus_on_click (GtkWidget *widget, gboolean focus_on_click); -- 2.30.2